package com.feicheng.controller.shop.wx.app.client;


import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import javax.servlet.http.HttpServletRequest;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.feicheng.common.constant.Constant;
import com.feicheng.common.exception.SystemException;
import com.feicheng.common.result.ResultInfo;
import com.feicheng.common.token.TokenContainer;
import com.feicheng.controller.BaseController;
import com.feicheng.persistence.entity.Account;
import com.feicheng.persistence.entity.Client;
import com.feicheng.persistence.entity.ClientDeposit;
import com.feicheng.persistence.entity.DepositBackRequest;
import com.feicheng.persistence.entity.DepositRecord;
import com.feicheng.persistence.entity.Order;
import com.feicheng.persistence.entity.PaymentRecord;
import com.feicheng.persistence.model.ClientDepositPlus;
import com.feicheng.persistence.service.IAccountService;
import com.feicheng.persistence.service.IClientDepositService;
import com.feicheng.persistence.service.IDepositBackRequestService;
import com.feicheng.persistence.service.IDepositRecordService;
import com.feicheng.persistence.service.IOrderService;
import com.feicheng.persistence.service.IPaymentRecordService;
import com.feicheng.service.IFClientService;
import com.feicheng.service.IFStoreService;

import lombok.extern.slf4j.Slf4j;

/**
 * <p>
 *  前端控制器
 * </p>
 *
 * @author cailongyang
 * @since 2021-12-02
 */
@RestController("/wx/app/client/client-deposit")
@RequestMapping("/wx/app/client/client-deposit")
@Slf4j
public class ClientDepositController extends BaseController {
	@Autowired
    HttpServletRequest request;

    @Autowired
    IFStoreService fStoreService;

    @Autowired
    IFClientService fClientService;

    @Autowired
    IAccountService accountService;

    @Autowired
    IDepositRecordService depositRecordService;

    @Autowired
    IClientDepositService clientDepositService;

    @Autowired
    IPaymentRecordService paymentRecordService;

    @Autowired
    IDepositBackRequestService depositBackRequestService;
    
    @Autowired
    IOrderService orderService;

    @Autowired
    TokenContainer tokenContainer;
    
    @PutMapping("/info")
    public ResultInfo updateClientDepoist(ClientDeposit clientDeposit) {
    	
    	if (null == clientDeposit.getClientId()) {
    		throw new SystemException("客户ID缺失");
    	}
    	
    	if (null == clientDeposit.getDepositId()) {
    		throw new SystemException("押金记录ID缺失");
    	}
    	
    	QueryWrapper<Order> orderQueryWrapper = new QueryWrapper<>();
    	orderQueryWrapper.eq("client_id", clientDeposit.getClientId());
    	orderQueryWrapper.and(wrapper -> wrapper.eq("statu", "ST").or().eq("statu", "UNPAY"));
    	List<Order> orderList = orderService.list(orderQueryWrapper);
    	if (null != orderList && orderList.size() > 0) {
    		throw new SystemException("您有未结算的订单，请先完成订单结算再进行退押金申请。");
    	}
    	
    	UpdateWrapper<ClientDeposit> clientDepositWrapper = new UpdateWrapper<>();
    	clientDepositWrapper.eq("client_id", clientDeposit.getClientId());
    	clientDepositWrapper.eq("deposit_id", clientDeposit.getDepositId());
    	
    	ClientDeposit newClientDeposit = new ClientDeposit();
    	
    	newClientDeposit.setStatu(clientDeposit.getStatu());
    	
    	clientDepositService.update(newClientDeposit, clientDepositWrapper);
    	
    	return ResultInfo.success();
    	
    }
    
    
    @GetMapping("/info/v2")
    public ResultInfo getClientDepositInfoV2() {
    	JSONObject result = new JSONObject();
    	Client currentClient = super.currentClient();
        QueryWrapper<Account> accountQueryWrapper = new QueryWrapper<Account>();
        accountQueryWrapper.eq(Constant.ENTITY.ACCOUNT.CLIENT_ID, currentClient.getClientId());

        List<Account> accounts = accountService.list(accountQueryWrapper);
        result.put(Constant.ENTITY.ACCOUNT.TABLE, accounts.get(0));
        
        QueryWrapper<ClientDepositPlus> clientDepositPlusWrapper = new QueryWrapper<>();
        clientDepositPlusWrapper.eq(Constant.ENTITY.DEPOSIT_RECORD.TYPE, Constant.VAL.DEPOSIT.INS);
        clientDepositPlusWrapper.eq(Constant.ENTITY.CLIENT_DEPOSIT.CLIENT_ID, currentClient.getClientId());
        clientDepositPlusWrapper.orderByDesc(Constant.ENTITY.DEPOSIT_RECORD.CT);
        List<ClientDepositPlus> depositRecords = depositRecordService.getClientDepositPlus(clientDepositPlusWrapper);
        result.put(Constant.ENTITY.DEPOSIT_RECORD.TABLE, depositRecords);

        JSONObject paymentRecordMap = new JSONObject();
        for(DepositRecord depositRecord : depositRecords) {
            PaymentRecord paymentRecord = paymentRecordService.getById(depositRecord.getPayId());
            paymentRecordMap.put(depositRecord.getDepositId().toString(), paymentRecord);
        }
        result.put(Constant.ENTITY.PAYMENT_RECORD.TABLE, paymentRecordMap);

        QueryWrapper<DepositBackRequest> depositBackRequestQueryWrapper =
                new QueryWrapper<>();
        depositBackRequestQueryWrapper.eq(Constant.ENTITY.DEPOSIT_BACK_REQUEST.CLIENT_ID, currentClient.getClientId());
        result.put(Constant.ENTITY.DEPOSIT_BACK_REQUEST.TABLE, depositBackRequestService.list(depositBackRequestQueryWrapper));

        return ResultInfo.success(result); 
    }
    

    @GetMapping("/info")
    public ResultInfo getClientDepositInfo() {

        JSONObject result = new JSONObject();
        Client currentClient = super.currentClient();
        QueryWrapper<Account> accountQueryWrapper = new QueryWrapper<Account>();
        accountQueryWrapper.eq(Constant.ENTITY.ACCOUNT.CLIENT_ID, currentClient.getClientId());

        List<Account> accounts = accountService.list(accountQueryWrapper);
        result.put(Constant.ENTITY.ACCOUNT.TABLE, accounts.get(0));

        QueryWrapper<ClientDeposit> clientDepositQueryWrapper = new QueryWrapper<>();
        clientDepositQueryWrapper.eq(Constant.ENTITY.CLIENT_DEPOSIT.CLIENT_ID, currentClient.getClientId());
        List<ClientDeposit> clientDeposits = clientDepositService.list(clientDepositQueryWrapper);
        Set<Integer> depositIdSet = new HashSet<>();
        for (ClientDeposit clientDeposit : clientDeposits) {
            depositIdSet.add(clientDeposit.getDepositId());
        }

        if (depositIdSet.size() > 0) {
            QueryWrapper<DepositRecord> depositRecordQueryWrapper = new QueryWrapper<>();
            depositRecordQueryWrapper.isNotNull(Constant.ENTITY.DEPOSIT_RECORD.PAY_ID);
            depositRecordQueryWrapper.in(Constant.ENTITY.DEPOSIT_RECORD.DEPOSIT_ID, depositIdSet);
            List<DepositRecord> depositRecords = depositRecordService.list(depositRecordQueryWrapper);
            result.put(Constant.ENTITY.DEPOSIT_RECORD.TABLE, depositRecords);

            JSONObject paymentRecordMap = new JSONObject();
            for(DepositRecord depositRecord : depositRecords) {
                PaymentRecord paymentRecord = paymentRecordService.getById(depositRecord.getPayId());
                paymentRecordMap.put(depositRecord.getDepositId().toString(), paymentRecord);
            }
            result.put(Constant.ENTITY.PAYMENT_RECORD.TABLE, paymentRecordMap);
        } else {
            result.put(Constant.ENTITY.DEPOSIT_RECORD.TABLE, new ArrayList<>());
            result.put(Constant.ENTITY.PAYMENT_RECORD.TABLE, new JSONObject());
        }

        QueryWrapper<DepositBackRequest> depositBackRequestQueryWrapper =
                new QueryWrapper<>();
        depositBackRequestQueryWrapper.eq(Constant.ENTITY.DEPOSIT_BACK_REQUEST.CLIENT_ID, currentClient.getClientId());
        result.put(Constant.ENTITY.DEPOSIT_BACK_REQUEST.TABLE, depositBackRequestService.list(depositBackRequestQueryWrapper));

        return ResultInfo.success(result);
    }
}
